<template>
  <el-cascader
    v-if="type == 'select'"
    style="width: 100%"
    :options="options"
    v-model="region"
    clearable
    :props="{ checkStrictly: true, value: 'id', multiple: multiple }"
    :placeholder="placeholder"
    :disabled="readonly"
    @change="change"
  ></el-cascader>
  <span v-else>{{ name }}</span>
</template>

<script>
import landApi from '@/api/land/land'

export default {
  props: {
    placeholder: {
      type: String,
      default: '请选择'
    },
    value: {
      type: String | Array,
      default: ''
    },
    disabled: {
      type: Boolean,
      default: false
    },
    type: {
      type: String,
      default: 'select'
    },
    // 是否可以多选
    multiple: {
      type: Boolean,
      default: false
    },
    // 是否要全路径
    allPath: {
      type: Boolean,
      default: true
    }
  },
  watch: {
    value: {
      async handler(val) {
        if (val) {
          if (!this.multiple) {
            if (typeof val == 'string' && val !== '') {
              val.includes(',') ? (this.region = val.split(',')) : (this.region = [val])
            } else if (val.length) this.region = val
          } else if (this.multiple && this.allPath) {
            const convertedData = this.value.map((arr) => arr.join(','))
            this.region = convertedData.join(';')
          } else if (this.multiple && !this.allPath) {
            if (this.options.length == 0) await this.getArea()
            this.region = this.findParentIds(this.options, val)
          }
        } else this.region = []
        if (this.type == 'text') this.getLabel()
      },
      immediate: true
    },
    disabled: {
      handler(val) {
        this.readonly = val
      },
      immediate: true
    }
  },
  data() {
    return {
      options: [],
      region: [],
      readonly: false,
      name: ''
    }
  },
  async created() {
    if (this.$store.state.user.areaList) this.options = this.$store.state.user.areaList
    else await this.getArea()

    if (this.type == 'text') this.getLabel()
  },
  methods: {
    async getArea() {
      const { data } = await landApi.getArea()
      this.options = data
      this.$store.commit('SET_AREA_LIST', data)
    },
    change() {
      if (this.region.length > 0) {
        if (this.multiple && this.allPath) {
          const convertedData = this.region.map((arr) => arr.join(','))
          const region = convertedData.join(';')
          this.$emit('update:value', region)
          this.$emit('change', region)
        } else if (this.multiple && !this.allPath) {
          const item = this.region.map((subArray) => subArray.slice(-1)[0]).join(',')
          this.$emit('update:value', item)
          this.$emit('change', item)
        } else if (!this.multiple) {
          this.region.length == 1
            ? this.$emit('update:value', this.region.join(''))
            : this.$emit('update:value', this.region.join(','))
          this.$emit('change', this.region[this.region.length - 1])
        }
      } else this.$emit('update:value', '')
      this.getLabel()
    },
    getLabel() {
      let arr = []
      // 转成一维数组
      const flatten = (arr) =>
        arr.flatMap(({ children, ...rest }) => [rest, ...(Array.isArray(children) ? flatten(children) : [])])

      const options = flatten(this.options)
      for (let i of this.region) {
        for (let v of options) {
          if (i == v.id) arr.push(v.label)
        }
      }
      this.name = arr.join('/')
    },
    findParentIds(data, targetIds, parentIds = []) {
      const idsArray = targetIds.split(',') // 将逗号分隔的值拆分成数组
      const result = []

      for (const id of idsArray) {
        const parentArray = []
        for (const item of data) {
          const parentIdsForItem = this.findParentIdsRecursive(item, id, parentIds)
          if (parentIdsForItem) {
            parentArray.push(...parentIdsForItem)
            break // 找到一个匹配的上级就停止
          }
        }
        result.push(parentArray)
      }

      return result
    },
    findParentIdsRecursive(node, targetId, parentIds) {
      if (node.id === targetId) {
        return [...parentIds, node.id]
      } else if (node.children && node.children.length > 0) {
        for (const child of node.children) {
          const result = this.findParentIdsRecursive(child, targetId, [...parentIds, node.id])
          if (result) {
            return result
          }
        }
      }
      return null
    }
  }
}
</script>

<style></style>